<template>
	<div class="ves-box">
		<div class="ves-toolbar">
			<template v-for="(item) in options">
				<el-divider direction="vertical" v-if="item.divider"></el-divider>
				<el-button 
					v-else
					size="mini" 
					:title="item.label" 
					@click="callFn(item)">
					<template v-if="item.label !== 'Toggle Preview'">
						<i class="al-iconfont" v-html="item.icon"></i>
					</template>
					<template v-else>
						<i class="al-iconfont open-eye" v-if="openPreview">&#xe61f;</i>
						<i class="al-iconfont" v-else>&#xe656;</i>
					</template>
				</el-button>
			</template>
		</div>
		<div class="ves-content">
			<textarea
				ref="ves_edit" 
				v-model="markString">
			</textarea>
			<div v-html="htmlString" v-if="openPreview" class="preview"></div>
		</div>
		<div class="ves-footer clearfix">
			<div style="float: left;">
				VES Markdown Editor
			</div>
			words: {{count}}
		</div>
	</div>
</template>

<script>
	import marked from 'marked'
	import hljs from 'highlight.js'
	import ('highlight.js/styles/atom-one-light.css')
	import './css/ves-markdown.css'
	export default {
		name: 'ves-markdown',
		data() {
			return {
				markString: '',
				htmlString: '',
				openPreview: false,
				count: 0,
				options: require('./js/config.js')
			}
		},
		watch: {
			// 监听是否实时预览
			openPreview: function (value) {
				let obj = this.$refs.ves_edit;
				if (value === true) {
					obj.style.width = '50%';
					obj.style.display = "inline-block";
				} else {
					obj.style.width = '100%';
					obj.style.display = "block";
				}
			},
			// 监听编辑内容变化
			markString: function (value) {
				marked.setOptions({
					renderer: new marked.Renderer(),
					gfm: true,
					tables: true,
					breaks: true,
					pedantic: false,
					sanitize: false,
					smartLists: true,
					smartypants: false
				})
				this.htmlString = marked(value);
				// 传递内容
				this.$emit("handleContent", this.htmlString,value);
				// 重新计算字符长度
				this.countWords();
			},
			// 高亮显示
			htmlString: function (value) {
				this.$nextTick(() => {
					const codes = document.querySelectorAll(".html_body pre code");
					codes.forEach(elem => {
						elem.innerHTML = "<ul><li>" + elem.innerHTML.replace(/\n/g, "\n</li><li>") + "\n</li></ul>"
						hljs.highlightBlock(elem);
					});
				});
			}
		},
		created() {
			this.options.map(item => {
				const reg1 = /^\w+/g;
				const reg2 = /\(([^)]+)\)/;
				if (item.method) {
					item.fn = item.method.match(reg1)[0];
				}
			})
		},
		mounted() {
			// 初始赋值
			this.markString = "**Hello World**";
		},
		methods: {
			callFn(item) {
				if (item.fn) {
					this[item.fn].apply(this);
				}
			},
			// 统计字数
			countWords() {
				this.count = this.markString.length;
			},
			// 全部清空
			emptyAll() {
				this.$confirm('请确认是否清空所有文本内容', '全部清空', {
					confirmButtonText: '确定',
					cancelButtonText: '取消',
					type: 'warning',
				}).then(() => {
					this.markString = '';
				}).catch((res) => {
					console.log(res);
				});
			},
			// 加粗
			toBold() {
				this.changeSelectedText("**","**");
			},
			// 斜体
			toItalic() {
				this.changeSelectedText("***","***");
			},
			// 标题
			toHeading() {
				this.changeInsertText('# ');
			},
			// 删除线
			toStrikethrough() {
				this.changeSelectedText("~~","~~");
			},
			// 下划线
			toUnderline() {
				this.changeSelectedText("<u>","</u>");
			},
			// 引号
			toQuote() {
				this.changeInsertText('> ');
			},
			// 通用列表
			toGenericList() {
				this.changeInsertText('* ');
			},
			// 编号列表
			toNumberedList() {
				this.changeInsertText('1. ');
			},
			// 链接
			toLink() {
				this.changeInsertText('[](http://)',1);
			},
			// 图片
			toImage() {
				this.changeInsertText('![](http://)',2);
			},
			// 实时预览
			togglePreview() {
				if (this.openPreview) {
					this.openPreview = false;
				} else {
					this.openPreview = true;
				}
			},
			changeSelectedText(startString,endString) {
				let t = this.$refs.ves_edit;
				if (window.getSelection) {
					if (t.selectionStart != undefined && t.selectionEnd != undefined) {
						let str1 = t.value.substring(0, t.selectionStart);
						let str2 = t.value.substring(t.selectionStart, t.selectionEnd);
						let str3 = t.value.substring(t.selectionEnd);
						// 拼接内容
						let result = str1 + startString + str2 + endString + str3;
						t.value = result;
						this.markString = t.value;
					}
				}
				this.$refs.ves_edit.focus();
			},
			changeInsertText(val,len) {
				let obj = this.$refs.ves_edit;
				let oldVal = obj.value;
				obj.value += val;
				if (len > 0) {
					obj.selectionStart = oldVal.length + len;
					obj.selectionEnd = oldVal.length + len;
				}
				this.markString = obj.value;
				obj.focus();
			}
		}
	}
</script>
